<?php

/* ========================================================================= */
/* This file is part of the HypnoPHP Framework Library                       */
/* Copyright (c) 2009-2010, Radu Buzea                                       */
/* ========================================================================= */

/**
* @author Radu Buzea
* @copyright Copyright (c) 2009-2010, Radu Buzea (www.hypnosis.ro)
* @license GNU Lesser General Public License (www.gnu.org/copyleft/lesser.html)
* @package HypnoPHP
* @category Core
* @version 1.0.3
*/

// ============================================================================
// Interface: IBaseDb
// ============================================================================

interface IBaseDb
{
	public function connect();
	public function disconnect();
	public function hasError();
	public function errorNum();
	public function errorTxt();
	public function query($sql);
	public function fetchArray($result);
	public function fetchRow($result);
	public function fetchAssoc($result);
	public function fetchObject($result);
	public function fetchField($result, $index = 0);
	public function fieldLength($result, $index = 0);
	public function fieldFlags($result, $index = 0);
	public function freeResult($result);
	public function numRows($result);
	public function listFields($table_name, $schema = '');
	public function insertId();
	public function tablesList();
	public function tableExists($table_name);
	public function setCharset($charset);
	public function escapeStr($str);
	public function escapeNames($str);
	public function enumTypes();
	public function checkType($type = '');
	public function smartQuote($entity, $type = '');
}


// ============================================================================
// Abstract class: HBaseDb
// ============================================================================

abstract class HBaseDb extends HBaseObject implements IBaseDb
{
	protected $__auto_quote_identifiers = true;
	public $last_sql = '';

	/**
	* Class destructor
	*
	* @return void
	*/
	public function __destruct()
	{
		$this->disconnect();
		parent::__destruct();
	}

	# ###########################################################################

	/**
	* Initialize the object properties
	*
	* @return void
	*/
	public function __initialize()
	{
		$this->db_host = '';
		$this->db_name = '';
		$this->db_user = '';
		$this->db_pass = '';
		$this->db_system = '';
		$this->db_keep_alive = true;
		$this->db_auto_connect = false;
		$this->db_link_id = 0;
		$this->db_selected = false;
		$num_arg = func_num_args();
		if ($num_arg > 0) {
			$func_arg = func_get_arg(0);
			if (is_array($func_arg) && isset($func_arg[0])) {
				$func_arg = $func_arg[0];
				if (is_int($func_arg) && $func_arg >= 0) {
					$this->connectionSettings($func_arg);
				} else if (is_array($func_arg) && !isset($func_arg[0])) {
					if (isset($func_arg['db_host'])) {
						$this->db_host = $func_arg['db_host'];
					}
					if (isset($func_arg['db_name'])) {
						$this->db_name = $func_arg['db_name'];
					}
					if (isset($func_arg['db_user'])) {
						$this->db_user = $func_arg['db_user'];
					}
					if (isset($func_arg['db_pass'])) {
						$this->db_pass = $func_arg['db_pass'];
					}
					if (isset($func_arg['db_system'])) {
						$this->db_system = strtolower(trim($func_arg['db_system']));
					}
					if (isset($func_arg['db_keep_alive'])) {
						$this->db_keep_alive = boolval($func_arg['db_keep_alive']);
					}
					if (isset($func_arg['db_auto_connect'])) {
						$this->db_auto_connect = boolval($func_arg['db_auto_connect']);
					}
					if (isset($func_arg['db_charset'])) {
						$db_charset = trim($func_arg['db_charset']);
					}
				}
			}
		}
		if ($this->db_auto_connect) {
			$this->connect();
			if (isset($db_charset) && $db_charset != '') {
				$this->setCharset($db_charset);
			}
		}
	}

	# ###########################################################################

	/**
	* Select the database connection settings from the HApplication global settings
	*
	* @param integer $use_settings_inedx
	*/
	public function connectionSettings($use_settings_inedx = 0)
	{
		$db_conns = HApplication::getConfig('db_connections');
		if (isset($db_conns[$use_settings_inedx]) && is_array($db_conns[$use_settings_inedx])) {
			$db_conn = $db_conns[$use_settings_inedx];
			$settings_cnt = 0;
			if (isset($db_conn['db_system'])) {
				$this->db_system = trim(strtolower($db_conn['db_system']));
				$settings_cnt++;
			}
			if (isset($db_conn['db_host'])) {
				$this->db_host = trim($db_conn['db_host']);
				$settings_cnt++;
			}
			if (isset($db_conn['db_user'])) {
				$this->db_user = $db_conn['db_user'];
				$settings_cnt++;
			}
			if (isset($db_conn['db_pass'])) {
				$this->db_pass = $db_conn['db_pass'];
			}
			if (isset($db_conn['db_name'])) {
				$this->db_name = trim($db_conn['db_name']);
				$settings_cnt++;
			}
			if (isset($db_conn['db_keep_alive'])) {
				$this->db_keep_alive = boolval($db_conn['db_keep_alive']);
			}
			if (isset($db_conn['db_auto_connect'])) {
				$this->db_auto_connect = boolval($db_conn['db_auto_connect']);
			}
			return ($settings_cnt == 4);
		}
		return false;
	}

	# ###########################################################################

	/**
	* Check if a table exists in the database
	*
	* @param string $table_name
	* @return bool
	*/
	public function tableExists($table_name)
	{
		if (!is_string($table_name)) { return false; }
		$table_name = trim($table_name);
		if ($table_name == '') { return false; }
		$tables = $this->tablesList();
		return array_key_exists($table_name, $tables) || in_array($table_name, $tables);
	}

	# ###########################################################################

	/**
	* Check if the application is connected to the database server
	*
	* @return bool
	*/
	public function isConnected()
	{
		if ($this->db_link_id === false) { return false; }
		return (is_resource($this->db_link_id));
	}

	# ###########################################################################

	/**
	* Check if the database was selected
	*
	* @return bool
	*/
	public function isDatabaseSelected()
	{
		return ($this->db_selected);
	}

	# ###########################################################################

	/**
	* Check if the application is connected to the database server
	* and the database was selected
	*
	* @return bool
	*/
	public function isReady()
	{
		return ($this->isConnected() && $this->isDatabaseSelected());
	}

	# ###########################################################################

	/**
	* Check if the database server reported an error after the last
	* executed query action
	*
	* @return bool
	*/
	public function hasError()
	{
		return ($this->errorNum() > 0);
	}

	# ###########################################################################

	/**
	* Close the database server connection. Alias for 'disconnect'
	*
	* @return void
	*/
	public function close()
	{
		$this->disconnect();
	}

	# ###########################################################################

}
